package com.frcdi.qms.system.service.impl;

import com.frcdi.qms.common.constant.UserConstants;
import com.frcdi.qms.common.core.domain.model.LoginUser;
import com.frcdi.qms.common.exception.ServiceException;
import com.frcdi.qms.common.utils.SecurityUtils;
import com.frcdi.qms.common.utils.StringUtils;
import com.frcdi.qms.equipment.domain.EquipmentBase;
import com.frcdi.qms.equipment.mapper.EquipmentBaseMapper;
import com.frcdi.qms.masterdata.domain.ChangeExecution;
import com.frcdi.qms.masterdata.domain.Material;
import com.frcdi.qms.masterdata.domain.Method;
import com.frcdi.qms.masterdata.mapper.ChangeExecutionMapper;
import com.frcdi.qms.masterdata.mapper.MaterialMapper;
import com.frcdi.qms.masterdata.mapper.MethodMapper;
import com.frcdi.qms.system.domain.SysDigitalSign;
import com.frcdi.qms.system.domain.vo.DigitalSignVO;
import com.frcdi.qms.system.mapper.SysDigitalSignMapper;
import com.frcdi.qms.system.service.ISysDigitalSignService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

/**
 * 电子签名Service业务层处理
 *
 * @author cell
 * @date 2023-10-13
 */
@Service
public class SysDigitalSignServiceImpl implements ISysDigitalSignService {
    private static final Logger log = LoggerFactory.getLogger(SysDigitalSignServiceImpl.class);
    @Autowired
    private SysDigitalSignMapper sysDigitalSignMapper;

    @Autowired
    private ChangeExecutionMapper executionMapper;

    @Autowired
    private MaterialMapper materialMapper;

    @Autowired
    private MethodMapper methodMapper;

    @Autowired
    private EquipmentBaseMapper equipmentBaseMapper;

    /**
     * 查询电子签名
     *
     * @param signId 电子签名主键
     * @return 电子签名
     */
    @Override
    public SysDigitalSign selectSysDigitalSignBySignId(Long signId) {
        return sysDigitalSignMapper.selectSysDigitalSignBySignId(signId);
    }

    /**
     * 查询电子签名列表
     *
     * @param sysDigitalSign 电子签名
     * @return 电子签名
     */
    @Override
    public List<SysDigitalSign> selectSysDigitalSignList(SysDigitalSign sysDigitalSign) {
        return sysDigitalSignMapper.selectSysDigitalSignList(sysDigitalSign);
    }

    /**
     * 新增电子签名
     *
     * @param sysDigitalSign 电子签名
     * @return 结果
     */
    @Override
    public int insertSysDigitalSign(DigitalSignVO sysDigitalSign) {
        LoginUser loginUser = SecurityUtils.getLoginUser();
        if (!StringUtils.equals(sysDigitalSign.getUserName(), loginUser.getUsername())) {
            throw new ServiceException("用户名错误");
        }
        if (!SecurityUtils.matchesPassword(sysDigitalSign.getPassword(), loginUser.getPassword())) {
            throw new ServiceException("密码错误");
        }
        return sysDigitalSignMapper.insertSysDigitalSign(sysDigitalSign);
    }

    /**
     * 数字签名
     */
    @Transactional
    @Override
    public boolean digitalSign(DigitalSignVO signVO) {
        LoginUser loginUser = SecurityUtils.getLoginUser();
        if (!StringUtils.equals(signVO.getUserName(), loginUser.getUsername())) {
            throw new ServiceException("用户名错误");
        }
        if (!SecurityUtils.matchesPassword(signVO.getPassword(), loginUser.getPassword())) {
            throw new ServiceException("密码错误");
        }

        // 插入电子签名记录
        sysDigitalSignMapper.insertSysDigitalSign(signVO);
        // 修改变更执行单状态
        updateChangeExecutionStatus(signVO);

        // 签名完成 生效对应数据
        if (StringUtils.equals(UserConstants.EXECUTION_PASS, signVO.getSignStatus())) {
            switch (signVO.getChangeType()) {
                case UserConstants.EQUIPMENT: equipmentEffective(signVO); break;
                case UserConstants.METHOD: methodEffective(signVO); break;
                case UserConstants.MATERIAL: materialEffective(signVO); break;
            }
        }

        // 签名完成 驳回对应数据
        if (StringUtils.equals(UserConstants.EXECUTION_REJECTED, signVO.getSignStatus())) {
            switch (signVO.getChangeType()) {
                case UserConstants.EQUIPMENT: equipmentRefuse(signVO); break;
                case UserConstants.METHOD: methodRefuse(signVO); break;
                case UserConstants.MATERIAL: materialRefuse(signVO); break;
            }
        }
        return UserConstants.UNIQUE;
    }

    /**
     * 修改变更执行单状态
     */
    private void updateChangeExecutionStatus(DigitalSignVO signVO) {
        ChangeExecution changeExecution = new ChangeExecution();
        changeExecution.setExecutionId(signVO.getExecutionId());
        changeExecution.setStatus(signVO.getSignStatus());
        changeExecution.setUpdateBy(SecurityUtils.getLoginUser().getUsername());
        executionMapper.updateChangeExecution(changeExecution);
    }

    /**
     * 以下为生效
     */
    private void materialEffective(DigitalSignVO signVO) {
        Material material = new Material();
        material.setId(signVO.getAssociatedId());
        material.setStatus(UserConstants.NORMAL);
        material.setUpdateBy(SecurityUtils.getLoginUser().getUsername());
        materialMapper.updateMaterial(material);
    }

    private void methodEffective(DigitalSignVO signVO) {
        Method method = new Method();
        method.setMethodId(signVO.getAssociatedId());
        method.setStatus(UserConstants.NORMAL);
        method.setUpdateBy(SecurityUtils.getLoginUser().getUsername());
        methodMapper.updateMethod(method);
    }

    private void equipmentEffective(DigitalSignVO signVO) {
        EquipmentBase equipment = new EquipmentBase();
        equipment.setEquipmentId(signVO.getAssociatedId());
        equipment.setStatus(UserConstants.NORMAL);
        equipment.setUpdateBy(SecurityUtils.getLoginUser().getUsername());
        equipmentBaseMapper.updateEquipmentBase(equipment);
    }

    /**
     * 以下为驳回
     */
    private void materialRefuse(DigitalSignVO signVO) {
        Material material = new Material();
        material.setId(signVO.getAssociatedId());
        material.setAuditResult(UserConstants.NORMAL);
        material.setSend(UserConstants.SEND_REJECTED);
        material.setTaskStatus(UserConstants.TASK_NOT);
        material.setUpdateBy(SecurityUtils.getLoginUser().getUsername());
        materialMapper.updateMaterial(material);
    }

    private void methodRefuse(DigitalSignVO signVO) {
        Method method = new Method();
        method.setMethodId(signVO.getAssociatedId());
        method.setAuditResult(UserConstants.NORMAL);
        method.setSend(UserConstants.SEND_REJECTED);
        method.setTaskStatus(UserConstants.TASK_NOT);
        method.setUpdateBy(SecurityUtils.getLoginUser().getUsername());
        methodMapper.updateMethod(method);
    }

    private void equipmentRefuse(DigitalSignVO signVO) {
        EquipmentBase equipment = new EquipmentBase();
        equipment.setEquipmentId(signVO.getAssociatedId());
        equipment.setAuditResult(UserConstants.NORMAL);
        equipment.setSend(UserConstants.SEND_REJECTED);
        equipment.setTaskStatus(UserConstants.TASK_NOT);
        equipment.setUpdateBy(SecurityUtils.getLoginUser().getUsername());
        equipmentBaseMapper.updateEquipmentBase(equipment);
    }
}
